package ui;

import java.awt.Color;
import java.awt.Component;
import java.awt.Dimension;
import java.awt.Font;
import java.awt.GridLayout;
import java.awt.Image;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.io.File;
import java.io.IOException;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.LinkedList;
import java.util.Locale;

import javax.imageio.ImageIO;
import javax.swing.DefaultListCellRenderer;
import javax.swing.DefaultListModel;
import javax.swing.GroupLayout;
import javax.swing.ImageIcon;
import javax.swing.JButton;
import javax.swing.JCheckBox;
import javax.swing.JComboBox;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JList;
import javax.swing.JMenuBar;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.JSeparator;
import javax.swing.JScrollPane;
import javax.swing.JTabbedPane;
import javax.swing.JTable;
import javax.swing.JTextField;
import javax.swing.JTextPane;
import javax.swing.ListSelectionModel;
import javax.swing.UIManager;
import javax.swing.border.EtchedBorder;
import javax.swing.border.TitledBorder;
import javax.swing.event.DocumentEvent;
import javax.swing.event.DocumentListener;
import javax.swing.event.ListSelectionEvent;
import javax.swing.event.ListSelectionListener;
import javax.swing.GroupLayout.Alignment;
import javax.swing.LayoutStyle.ComponentPlacement;
import javax.swing.table.DefaultTableModel;
import javax.swing.table.TableRowSorter;

import controller.ItemController;
import controller.SupplierController;
import model.Item;
import model.ItemSupplier;
import model.ItemType;
import model.ItemTypeMeasurement;
import model.Outsider;
import util.ImagePanel;
import util.DoubleComparator;
import util.IntComparator;
import util.Menu;
import util.Number;

public class ItemUI implements ActionListener, ListSelectionListener
{
	private boolean startup = false;

	private static ItemUI instance = null;

	private ItemController itemCtrl;
	private SupplierController supplierCtrl;

	private JFrame frameItemUI;

	private JTabbedPane tabbedPane;

	private JPanel redPanel;

	private Image image = null;

	private ImagePanel newItem;
	private ImagePanel allItems;
	private ImagePanel itemTypes;
	private ImagePanel itemTypeMeasurements;

	private JTable allItemsTable;
	private JTable newItemTableSelected;
	private JTable newItemTableAll;

	private DefaultTableModel allItemsTableModel;
	private DefaultTableModel newItemModelSelected;
	private DefaultTableModel newItemModelAll;

	private JList<String> itemTypesEditListTypes;
	private JList<String> itemTypeMeasurementsEditList;
	private JList<String> allItemsInfoListOutsiders;

	private DefaultListModel<String> itemTypesEditListTypesModel;
	private DefaultListModel<String> itemTypesEditListTypeMeasurementsModel;
	private DefaultListModel<String> allItemsInfoListOutsidersModel;

	private JComboBox<String> allItemsComboBoxSearchTypes;
	private JComboBox<String> allItemsComboBoxSearchType;
	private	JComboBox<String> newItemComboBoxType;
	private JComboBox<String> editItemComboBoxType;
	private JComboBox<String> itemTypesNewComboBoxMeasurement;
	private JComboBox<String> itemTypesEditComboBoxMeasurement;

	private JButton newItemButtonCreateItem;
	private JButton allItemsButtonSearchClear;
	private JButton allItemsButtonEditItem;
	private JButton itemTypesNewButtonItemTypeAdd;
	private JButton itemTypesEditButtonItemTypeEdit;
	private JButton itemTypeMeasurementsNewButtonAdd;
	private JButton itemTypeMeasurementsEditButtonEdit;
	private JButton allItemsButtonEditOutsiders;
	private JButton statistics;

	private JCheckBox allItemsCheckBoxOnlyActiveItems;

	private JTextField allItemsTextFieldSearchFor;
	private JTextField newItemTextFieldName;
	private JTextField newItemTextFieldStock;
	private JTextField newItemTextFieldPrice;
	private JTextField newItemTextFieldDimensions;
	private JTextField itemTypesNewTextFieldItemTypeName;
	private JTextField itemTypesEditTextFieldItemTypeName;
	private JTextField itemTypeMeasurementsNewTextFieldValue;
	private JTextField itemTypeMeasurementsEditTextFieldValue;

	private JTextPane allItemsInfoValueDimensions;

	private JMenuBar menu;

	private Menu menuBar;

	private ArrayList<JTextField> newItemTextFields;
	private ArrayList<JTextField> editItemTextFields;
	private ArrayList<ItemType> itemTypeList;
	private ArrayList<ItemTypeMeasurement> itemTypeMeasurementList;
	private ArrayList<String> supplierFlagList;
	private ArrayList<Outsider> supplierList;
	private ArrayList<ItemSupplier> itemEditOutsidersList;

	//private HashMap<Outsider, Integer> newItemOutsiders;
	private ArrayList<ItemSupplier> newItemOutsiders;

	private JLabel allItemsInfoValueName;
	private JLabel allItemsInfoValuePrice;
	private JLabel allItemsInfoValueStock;
	private JLabel allItemsInfoValueOutsiders;
	private JLabel allItemsInfoValueType;

	private Dimension tableDimension;

	private double columnWidth;
	private double[] columnWidthOutsiders = { 0.8, 3, 0.5, 1 };

	private String newItemOutsiderTables [] = { "#", "Name", "" };
	private String newItemOutsiderStockTables [] = { "#", "Name", "", "" };
	private String allItemsColumns [] = { "#", "Name", "Stock", "", "Price", "Type" };

	private JButton allItemsButtonAddStock;

	private JTable allItemsEditItemOutsidersTable;

	private JButton allItemsButtonAddSupplier;
	private JButton btnBack;
	private JSeparator separator_3;
	private JSeparator separator_4;
	
	private backButton back;

	public void display()
	{
		frameItemUI.getContentPane().add(redPanel);

		redPanel.add(tabbedPane);

		tabbedPane.addTab("All Items", null, allItems, null);
		tabbedPane.addTab("New Item", null, newItem, null);
		tabbedPane.addTab("Item Types", null, itemTypes, null);
		tabbedPane.addTab("Item Type Measurements", null, itemTypeMeasurements, null);

		frameItemUI.setSize(800,420);
		frameItemUI.setLocationRelativeTo(null);
		frameItemUI.setVisible(true);
		frameItemUI.setResizable(false);
		
	}

	public ItemUI()
	{
		frameItemUI = new JFrame("Item UI");
		
		back = new backButton();
		back.setNumber("9");

		menuBar = Menu.getInstance();

		menu = menuBar.makeJMenuBar();

		frameItemUI.setJMenuBar(menu);

		redPanel = new JPanel();
		redPanel.setBackground(new Color(165, 42, 42));

		tabbedPane = new JTabbedPane();

		itemCtrl = new ItemController();
		supplierCtrl = new SupplierController();

		itemTypeList = new ArrayList<ItemType>();

		try
		{
			image = ImageIO.read(new File("img/background/background.jpg"));
		} 
		catch (IOException e)
		{
			msgError(null, "Could not load background image");
		}

		JLabel redPanelLabelTitle = new JLabel("Materials");

		redPanelLabelTitle.setForeground(Color.WHITE);
		redPanelLabelTitle.setFont(new Font("Arial Unicode MS", Font.BOLD, 20));
		
				statistics = new JButton();
				statistics.setLocation(590, 327);
				statistics.setSize(100, 20);
				statistics.setOpaque(false);
				statistics.setText("Statistics");
				statistics.addActionListener(this);
		
		btnBack = new JButton();
		btnBack.setText("Back");
		btnBack.setOpaque(false);
		btnBack.addActionListener(this);
		
		GroupLayout gl_redTitle = new GroupLayout(redPanel);
		gl_redTitle.setHorizontalGroup(
			gl_redTitle.createParallelGroup(Alignment.LEADING)
				.addGroup(gl_redTitle.createSequentialGroup()
					.addGroup(gl_redTitle.createParallelGroup(Alignment.LEADING)
						.addGroup(gl_redTitle.createSequentialGroup()
							.addContainerGap()
							.addComponent(redPanelLabelTitle))
						.addComponent(tabbedPane, GroupLayout.PREFERRED_SIZE, 794, GroupLayout.PREFERRED_SIZE))
					.addContainerGap())
				.addGroup(Alignment.TRAILING, gl_redTitle.createSequentialGroup()
					.addContainerGap()
					.addComponent(btnBack, GroupLayout.PREFERRED_SIZE, 100, GroupLayout.PREFERRED_SIZE)
					.addPreferredGap(ComponentPlacement.RELATED, 574, Short.MAX_VALUE)
					.addComponent(statistics, GroupLayout.PREFERRED_SIZE, 100, GroupLayout.PREFERRED_SIZE)
					.addGap(20))
		);
		gl_redTitle.setVerticalGroup(
			gl_redTitle.createParallelGroup(Alignment.LEADING)
				.addGroup(gl_redTitle.createSequentialGroup()
					.addComponent(redPanelLabelTitle)
					.addPreferredGap(ComponentPlacement.RELATED)
					.addComponent(tabbedPane, GroupLayout.PREFERRED_SIZE, 309, GroupLayout.PREFERRED_SIZE)
					.addGap(5)
					.addGroup(gl_redTitle.createParallelGroup(Alignment.BASELINE)
						.addComponent(statistics, GroupLayout.PREFERRED_SIZE, 20, GroupLayout.PREFERRED_SIZE)
						.addComponent(btnBack, GroupLayout.PREFERRED_SIZE, 20, GroupLayout.PREFERRED_SIZE))
					.addContainerGap(22, Short.MAX_VALUE))
		);

		redPanel.setLayout(gl_redTitle);

		/******************************************************
		 * 
		 * New Item pane
		 * 
		 ******************************************************/

		newItem = new ImagePanel(image);

		JLabel newItemLabelName = new JLabel("Item Name:");
		JLabel newItemLabelStock = new JLabel("Item Stock:");
		JLabel newItemLabelPrice = new JLabel("Item Price:");
		JLabel newItemLabelType = new JLabel("Item Type:");
		JLabel newItemLabelOutsider = new JLabel("Item Outsider(s):");
		JLabel newItemLabelDimensions = new JLabel("Item Dimensions:");
		JLabel newItemLabelAllOutsiders = new JLabel("All Outsiders:");

		newItemTextFieldName = new JTextField();
		newItemTextFieldStock = new JTextField();
		newItemTextFieldStock.setEnabled(false);
		newItemTextFieldPrice = new JTextField();
		newItemTextFieldDimensions = new JTextField();

		newItemComboBoxType = new JComboBox<String>();
		newItemComboBoxType.setOpaque(false);		

		newItemButtonCreateItem = new JButton("Create Item");
		newItemButtonCreateItem.setOpaque(false);
		newItemButtonCreateItem.addActionListener(this);

		//newItemOutsiders = new ArrayList<Outsider>();
		//newItemOutsiders =  new HashMap<Outsider, Integer>();
		newItemOutsiders = new ArrayList<ItemSupplier>();

		newItemTextFields = new ArrayList<JTextField>();
		newItemTextFields.add(newItemTextFieldName);
		newItemTextFields.add(newItemTextFieldStock);
		newItemTextFields.add(newItemTextFieldPrice);

		newItemModelAll = new DefaultTableModel(null, newItemOutsiderTables);
		newItemTableAll = new JTable(newItemModelAll)
		{
			private static final long serialVersionUID = 1L;

			public boolean isCellEditable(int rowIndex, int colIndex) 
			{
				return false;
			}

			public Class<?> getColumnClass(int column)   
			{   
				return getValueAt(0, column).getClass();   
			}
		};

		tableDimension = newItemTableAll.getPreferredSize(); 

		columnWidth = tableDimension.width / newItemOutsiderTables.length; 

		for (int i = 0; i < newItemOutsiderTables.length; i++)
			newItemTableAll.getColumnModel().getColumn(i).setPreferredWidth((int) (columnWidth*columnWidthOutsiders[i])); 

		newItemTableAll.addMouseListener(new MouseAdapter() 
		{
			public void mouseClicked(MouseEvent e) 
			{
				String quantity = JOptionPane.showInputDialog("Quantity the supplier has providen:");

				if (Number.isNumber(quantity))
				{
					int row = newItemTableAll.getSelectedRow();
					int supplierID = Integer.valueOf(String.valueOf(newItemTableAll.getValueAt(row, 0)));

					newItemModelAll.removeRow(row);

					try
					{
						ItemSupplier newSupplier = new ItemSupplier(supplierCtrl.searchSupplierID(supplierID), Integer.valueOf(quantity));

						newItemOutsiders.add(newSupplier);
						//newItemOutsiders.put(supplierCtrl.searchSupplierID(supplierID), Integer.valueOf(quantity));

						newItemUpdateSelectedOutsiders();
					}
					catch (SQLException e1)
					{
						msgError(null, "Could not move supplier");
					}
				}
				else 
				{
					msgError(null, "This is not a number");
				}
			}
		});

		JScrollPane newItemAllScroll = new JScrollPane(newItemTableAll);

		newItemModelSelected = new DefaultTableModel(null, newItemOutsiderStockTables);
		newItemTableSelected = new JTable(newItemModelSelected)
		{
			private static final long serialVersionUID = 1L;

			public boolean isCellEditable(int rowIndex, int colIndex) 
			{
				return false;
			}

			public Class<?> getColumnClass(int column)   
			{   
				return getValueAt(0, column).getClass();   
			}
		};

		for (int i = 0; i < newItemOutsiderStockTables.length; i++)
			newItemTableSelected.getColumnModel().getColumn(i).setPreferredWidth((int) (columnWidth*columnWidthOutsiders[i])); 

		newItemTableSelected.addMouseListener(new MouseAdapter() 
		{			
			public void mouseClicked(MouseEvent e) 
			{
				int row = newItemTableSelected.getSelectedRow();
				int supplierID = Integer.valueOf(String.valueOf(newItemTableSelected.getValueAt(row, 0)));

				try
				{
					Outsider movingOutsider = supplierCtrl.searchSupplierID(supplierID);

					itemOutsidersRemoveFromList(newItemOutsiders, supplierID);
					tableOutsidersAdd(newItemModelAll, movingOutsider);

					newItemUpdateSelectedOutsiders();
				}
				catch (SQLException e1)
				{
					msgError(null, "Could not load move supplier");
				}
			}
		});

		JScrollPane newItemSelectedScroll = new JScrollPane(newItemTableSelected);

		GroupLayout gl_newItem = new GroupLayout(newItem);
		gl_newItem.setHorizontalGroup(
				gl_newItem.createParallelGroup(Alignment.LEADING)
				.addGroup(gl_newItem.createSequentialGroup()
						.addContainerGap()
						.addGroup(gl_newItem.createParallelGroup(Alignment.LEADING)
								.addGroup(gl_newItem.createSequentialGroup()
										.addGroup(gl_newItem.createParallelGroup(Alignment.LEADING)
												.addComponent(newItemLabelName)
												.addComponent(newItemLabelStock)
												.addComponent(newItemLabelPrice))
												.addGap(37)
												.addGroup(gl_newItem.createParallelGroup(Alignment.LEADING, false)
														.addComponent(newItemTextFieldStock)
														.addComponent(newItemTextFieldName, GroupLayout.DEFAULT_SIZE, 129, Short.MAX_VALUE)
														.addComponent(newItemTextFieldPrice)))
														.addGroup(gl_newItem.createSequentialGroup()
																.addGroup(gl_newItem.createParallelGroup(Alignment.LEADING)
																		.addComponent(newItemLabelDimensions)
																		.addComponent(newItemLabelType))
																		.addPreferredGap(ComponentPlacement.UNRELATED)
																		.addGroup(gl_newItem.createParallelGroup(Alignment.LEADING)
																				.addComponent(newItemComboBoxType, GroupLayout.PREFERRED_SIZE, 132, GroupLayout.PREFERRED_SIZE)
																				.addComponent(newItemButtonCreateItem, GroupLayout.PREFERRED_SIZE, 114, GroupLayout.PREFERRED_SIZE)
																				.addComponent(newItemTextFieldDimensions, GroupLayout.DEFAULT_SIZE, 130, Short.MAX_VALUE))))
																				.addGap(63)
																				.addGroup(gl_newItem.createParallelGroup(Alignment.LEADING)
																						.addComponent(newItemLabelOutsider)
																						.addComponent(newItemSelectedScroll, GroupLayout.PREFERRED_SIZE, 217, GroupLayout.PREFERRED_SIZE))
																						.addGap(18)
																						.addGroup(gl_newItem.createParallelGroup(Alignment.LEADING)
																								.addComponent(newItemAllScroll, GroupLayout.DEFAULT_SIZE, 247, Short.MAX_VALUE)
																								.addComponent(newItemLabelAllOutsiders))
																								.addContainerGap())
				);
		gl_newItem.setVerticalGroup(
				gl_newItem.createParallelGroup(Alignment.LEADING)
				.addGroup(gl_newItem.createSequentialGroup()
						.addGap(16)
						.addGroup(gl_newItem.createParallelGroup(Alignment.BASELINE)
								.addComponent(newItemLabelOutsider)
								.addComponent(newItemLabelAllOutsiders))
								.addPreferredGap(ComponentPlacement.RELATED)
								.addGroup(gl_newItem.createParallelGroup(Alignment.LEADING)
										.addGroup(gl_newItem.createSequentialGroup()
												.addGroup(gl_newItem.createParallelGroup(Alignment.BASELINE)
														.addComponent(newItemLabelName)
														.addComponent(newItemTextFieldName, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE))
														.addPreferredGap(ComponentPlacement.UNRELATED)
														.addGroup(gl_newItem.createParallelGroup(Alignment.BASELINE)
																.addComponent(newItemLabelStock)
																.addComponent(newItemTextFieldStock, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE))
																.addGap(11)
																.addGroup(gl_newItem.createParallelGroup(Alignment.BASELINE)
																		.addComponent(newItemLabelPrice)
																		.addComponent(newItemTextFieldPrice, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE))
																		.addGap(10)
																		.addGroup(gl_newItem.createParallelGroup(Alignment.BASELINE)
																				.addComponent(newItemLabelDimensions)
																				.addComponent(newItemTextFieldDimensions, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE))
																				.addPreferredGap(ComponentPlacement.UNRELATED)
																				.addGroup(gl_newItem.createParallelGroup(Alignment.BASELINE)
																						.addComponent(newItemComboBoxType, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE)
																						.addComponent(newItemLabelType))
																						.addGap(18)
																						.addComponent(newItemButtonCreateItem)
																						.addGap(61))
																						.addGroup(gl_newItem.createSequentialGroup()
																								.addGroup(gl_newItem.createParallelGroup(Alignment.BASELINE)
																										.addComponent(newItemSelectedScroll, GroupLayout.DEFAULT_SIZE, 169, Short.MAX_VALUE)
																										.addComponent(newItemAllScroll, GroupLayout.PREFERRED_SIZE, 168, GroupLayout.PREFERRED_SIZE))
																										.addGap(76))))
				);
		newItem.setLayout(gl_newItem);

		/******************************************************
		 * 
		 * All items pane
		 *
		 ******************************************************/

		allItems = new ImagePanel(image);

		allItemsTableModel = new DefaultTableModel(null, allItemsColumns);

		allItemsTable = new JTable(allItemsTableModel)
		{
			private static final long serialVersionUID = 1L;

			public boolean isCellEditable(int rowIndex, int colIndex) 
			{
				return false;
			}

			public Class<?> getColumnClass(int column)   
			{   
				return getValueAt(0, column).getClass();   
			}
		};
		allItemsTable.getSelectionModel().addListSelectionListener(this);

		TableRowSorter<DefaultTableModel> allItemsTableSorter  = new TableRowSorter<DefaultTableModel>((DefaultTableModel) allItemsTable.getModel());

		allItemsTableSorter.setComparator(0, new IntComparator());
		allItemsTableSorter.setComparator(2, new IntComparator());
		allItemsTableSorter.setComparator(4, new DoubleComparator());

		allItemsTable.setRowSorter(allItemsTableSorter);

		Dimension dim = allItemsTable.getPreferredSize(); 

		double width = dim.width / allItemsColumns.length; 
		double[] width_2 = { 0.5, 1.5, 1, 0.2, 1, 1 };

		for (int i = 0; i < allItemsColumns.length; i++)
			allItemsTable.getColumnModel().getColumn(i).setPreferredWidth((int) (width*width_2[i])); 

		allItemsTable.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
		JScrollPane allItemsTableScroll = new JScrollPane(allItemsTable);

		JLabel allItemsLabelSearchBy = new JLabel("Search by:");
		JLabel allItemsLabelSearchFor = new JLabel("Search for:");
		JLabel allItemsLabelSearchTypes = new JLabel("Search types:");

		allItemsComboBoxSearchType = new JComboBox<String>();
		allItemsComboBoxSearchType.setOpaque(false);
		allItemsComboBoxSearchType.addActionListener(this);
		allItemsComboBoxSearchType.addItem("Everything");
		allItemsComboBoxSearchType.addItem("Name");
		allItemsComboBoxSearchType.addItem("Outsider");
		allItemsComboBoxSearchType.addItem("City");
		allItemsComboBoxSearchType.addItem("Country");

		allItemsTextFieldSearchFor = new JTextField();
		allItemsTextFieldSearchFor.getDocument().addDocumentListener(new DocumentListener()
		{
			@Override
			public void insertUpdate(DocumentEvent e)
			{
				// most likely to never be used .. 
				searchItems();						
			}

			@Override
			public void changedUpdate(DocumentEvent e)
			{
				searchItems();
			}

			@Override
			public void removeUpdate(DocumentEvent e)
			{
				searchItems();
			}
		});

		allItemsButtonSearchClear = new JButton("Clear search");
		allItemsButtonSearchClear.setOpaque(false);
		allItemsButtonSearchClear.addActionListener(this);

		allItemsButtonEditItem = new JButton("Edit item");
		allItemsButtonEditItem.setOpaque(false);
		allItemsButtonEditItem.addActionListener(this);

		allItemsCheckBoxOnlyActiveItems = new JCheckBox("Only items with stock");
		allItemsCheckBoxOnlyActiveItems.setOpaque(false);
		allItemsCheckBoxOnlyActiveItems.setSelected(true);
		allItemsCheckBoxOnlyActiveItems.addActionListener(this);

		allItemsComboBoxSearchTypes = new JComboBox<String>();
		allItemsComboBoxSearchTypes.addActionListener(this);

		JPanel allItemsInfo = new JPanel();
		allItemsInfo.setOpaque(false);
		allItemsInfo.setAutoscrolls(true);
		allItemsInfo.setBorder(new TitledBorder(UIManager.getBorder("TitledBorder.border"), "Item info", TitledBorder.LEADING, TitledBorder.BELOW_TOP, null, UIManager.getColor("CheckBox.focus")));

		allItemsButtonAddStock = new JButton("Add stock");
		allItemsButtonAddStock.setOpaque(false);
		allItemsButtonAddStock.addActionListener(this);

		GroupLayout gl_allItems = new GroupLayout(allItems);
		gl_allItems.setHorizontalGroup(
				gl_allItems.createParallelGroup(Alignment.LEADING)
				.addGroup(gl_allItems.createSequentialGroup()
						.addContainerGap()
						.addGroup(gl_allItems.createParallelGroup(Alignment.LEADING)
								.addGroup(gl_allItems.createSequentialGroup()
										.addGroup(gl_allItems.createParallelGroup(Alignment.LEADING)
												.addComponent(allItemsLabelSearchTypes)
												.addComponent(allItemsLabelSearchBy)
												.addComponent(allItemsLabelSearchFor))
												.addGap(18)
												.addGroup(gl_allItems.createParallelGroup(Alignment.LEADING, false)
														.addComponent(allItemsComboBoxSearchTypes, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
														.addComponent(allItemsComboBoxSearchType, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
														.addComponent(allItemsTextFieldSearchFor, GroupLayout.DEFAULT_SIZE, 157, Short.MAX_VALUE))
														.addGap(18)
														.addGroup(gl_allItems.createParallelGroup(Alignment.LEADING)
																.addComponent(allItemsCheckBoxOnlyActiveItems)
																.addComponent(allItemsButtonSearchClear))
																.addPreferredGap(ComponentPlacement.RELATED, 74, Short.MAX_VALUE)
																.addGroup(gl_allItems.createParallelGroup(Alignment.LEADING, false)
																		.addComponent(allItemsButtonEditItem, GroupLayout.PREFERRED_SIZE, 79, GroupLayout.PREFERRED_SIZE)
																		.addComponent(allItemsButtonAddStock, Alignment.TRAILING)))
																		.addComponent(allItemsTableScroll, GroupLayout.DEFAULT_SIZE, 540, Short.MAX_VALUE))
																		.addGap(10)
																		.addComponent(allItemsInfo, GroupLayout.PREFERRED_SIZE, 219, GroupLayout.PREFERRED_SIZE)
																		.addContainerGap())
				);
		gl_allItems.setVerticalGroup(
				gl_allItems.createParallelGroup(Alignment.TRAILING)
				.addGroup(gl_allItems.createSequentialGroup()
						.addGroup(gl_allItems.createParallelGroup(Alignment.LEADING)
								.addGroup(gl_allItems.createSequentialGroup()
										.addGap(14)
										.addGroup(gl_allItems.createParallelGroup(Alignment.BASELINE)
												.addComponent(allItemsLabelSearchTypes)
												.addComponent(allItemsComboBoxSearchTypes, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE))
												.addPreferredGap(ComponentPlacement.RELATED)
												.addGroup(gl_allItems.createParallelGroup(Alignment.BASELINE)
														.addComponent(allItemsLabelSearchBy)
														.addComponent(allItemsComboBoxSearchType, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE)
														.addComponent(allItemsCheckBoxOnlyActiveItems)
														.addComponent(allItemsButtonAddStock))
														.addPreferredGap(ComponentPlacement.RELATED)
														.addGroup(gl_allItems.createParallelGroup(Alignment.LEADING)
																.addComponent(allItemsLabelSearchFor)
																.addGroup(gl_allItems.createParallelGroup(Alignment.BASELINE)
																		.addComponent(allItemsTextFieldSearchFor, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE)
																		.addComponent(allItemsButtonEditItem)
																		.addComponent(allItemsButtonSearchClear)))
																		.addPreferredGap(ComponentPlacement.RELATED)
																		.addComponent(allItemsTableScroll, GroupLayout.DEFAULT_SIZE, 173, Short.MAX_VALUE))
																		.addComponent(allItemsInfo, GroupLayout.DEFAULT_SIZE, 270, Short.MAX_VALUE))
																		.addContainerGap())
				);

		JLabel allItemsInfoLabelName = new JLabel("Name:");
		JLabel allItemsInfoLabelPrice = new JLabel("Price:");
		JLabel allItemsInfoLabelStock = new JLabel("Stock:");
		JLabel allItemsInfoLabelDimensions = new JLabel("Dimensions:");
		JLabel allItemsInfoOutsiders = new JLabel("Suppliers:");
		JLabel allItemsInfoLabelType = new JLabel("Type:");

		allItemsInfoValueName = new JLabel("n/a");
		allItemsInfoValuePrice = new JLabel("0");
		allItemsInfoValueStock = new JLabel("0");
		allItemsInfoValueDimensions = new JTextPane();
		allItemsInfoValueDimensions.setEditable(false);
		allItemsInfoValueDimensions.setOpaque(false);
		allItemsInfoValueOutsiders = new JLabel("0");
		allItemsInfoValueType = new JLabel("n/a");

		allItemsInfoListOutsidersModel = new DefaultListModel<String>();
		allItemsInfoListOutsiders = new JList<String>(allItemsInfoListOutsidersModel);
		allItemsInfoListOutsiders.setBorder(null);
		allItemsInfoListOutsiders.setBackground(UIManager.getColor("menu"));
		allItemsInfoListOutsiders.setCellRenderer(new DefaultListCellRenderer ()
		{
			private static final long serialVersionUID = 1L;

			@Override
			public Component getListCellRendererComponent(JList<?> list, Object value, int index, boolean isSelected, boolean cellHasFocus)
			{		        
				JLabel label = (JLabel) super.getListCellRendererComponent(list, value, index, isSelected, cellHasFocus);
				label.setIcon(new ImageIcon("img/flags/" + supplierFlagList.get(index) + ".png"));

				return label;
			}

		});

		JScrollPane allItemsInfoListOutsidersScrollPane = new JScrollPane();
		allItemsInfoListOutsidersScrollPane.setBorder(new EtchedBorder(EtchedBorder.LOWERED, null, null));
		allItemsInfoListOutsidersScrollPane.setOpaque(false);
		allItemsInfoListOutsidersScrollPane.setViewportView(allItemsInfoListOutsiders);

		allItemsButtonEditOutsiders = new JButton("Edit suppliers");
		allItemsButtonEditOutsiders.addActionListener(this);
		allItemsButtonEditOutsiders.setFont(new Font("Tahoma", Font.PLAIN, 9));

		JSeparator separator = new JSeparator();

		allItemsButtonAddSupplier = new JButton("Add a supplier");
		allItemsButtonAddSupplier.addActionListener(this);
		allItemsButtonAddSupplier.setEnabled(false);
		allItemsButtonAddSupplier.setOpaque(false);
		allItemsButtonAddSupplier.setFont(new Font("Tahoma", Font.PLAIN, 9));

		GroupLayout gl_allItemsInfo = new GroupLayout(allItemsInfo);
		gl_allItemsInfo.setHorizontalGroup(
			gl_allItemsInfo.createParallelGroup(Alignment.TRAILING)
				.addGroup(gl_allItemsInfo.createSequentialGroup()
					.addGroup(gl_allItemsInfo.createParallelGroup(Alignment.LEADING)
						.addGroup(Alignment.TRAILING, gl_allItemsInfo.createSequentialGroup()
							.addGap(10)
							.addGroup(gl_allItemsInfo.createParallelGroup(Alignment.LEADING)
								.addGroup(gl_allItemsInfo.createSequentialGroup()
									.addGroup(gl_allItemsInfo.createParallelGroup(Alignment.LEADING)
										.addGroup(gl_allItemsInfo.createParallelGroup(Alignment.LEADING)
											.addGroup(gl_allItemsInfo.createParallelGroup(Alignment.LEADING)
												.addGroup(gl_allItemsInfo.createSequentialGroup()
													.addGroup(gl_allItemsInfo.createParallelGroup(Alignment.LEADING)
														.addComponent(allItemsInfoLabelDimensions)
														.addComponent(allItemsInfoLabelStock, GroupLayout.DEFAULT_SIZE, 58, Short.MAX_VALUE))
													.addGap(27))
												.addGroup(gl_allItemsInfo.createSequentialGroup()
													.addPreferredGap(ComponentPlacement.RELATED)
													.addComponent(allItemsInfoLabelName)
													.addPreferredGap(ComponentPlacement.RELATED)))
											.addGroup(gl_allItemsInfo.createSequentialGroup()
												.addPreferredGap(ComponentPlacement.RELATED)
												.addComponent(allItemsInfoLabelType)
												.addPreferredGap(ComponentPlacement.RELATED)))
										.addGroup(gl_allItemsInfo.createSequentialGroup()
											.addPreferredGap(ComponentPlacement.RELATED)
											.addComponent(allItemsInfoLabelPrice)
											.addPreferredGap(ComponentPlacement.RELATED)))
									.addGroup(gl_allItemsInfo.createParallelGroup(Alignment.TRAILING)
										.addGroup(gl_allItemsInfo.createSequentialGroup()
											.addGroup(gl_allItemsInfo.createParallelGroup(Alignment.LEADING)
												.addComponent(allItemsInfoValueType)
												.addComponent(allItemsInfoValueStock, GroupLayout.PREFERRED_SIZE, 88, GroupLayout.PREFERRED_SIZE)
												.addComponent(allItemsInfoValueName))
											.addPreferredGap(ComponentPlacement.RELATED, 11, Short.MAX_VALUE))
										.addGroup(gl_allItemsInfo.createSequentialGroup()
											.addPreferredGap(ComponentPlacement.RELATED)
											.addComponent(allItemsInfoValuePrice, GroupLayout.DEFAULT_SIZE, 99, Short.MAX_VALUE))
										.addGroup(gl_allItemsInfo.createSequentialGroup()
											.addPreferredGap(ComponentPlacement.RELATED)
											.addComponent(allItemsInfoValueDimensions, GroupLayout.PREFERRED_SIZE, 98, GroupLayout.PREFERRED_SIZE))))
								.addGroup(gl_allItemsInfo.createSequentialGroup()
									.addComponent(allItemsInfoOutsiders)
									.addPreferredGap(ComponentPlacement.RELATED)
									.addComponent(allItemsInfoValueOutsiders, GroupLayout.PREFERRED_SIZE, 37, GroupLayout.PREFERRED_SIZE))
								.addGroup(gl_allItemsInfo.createSequentialGroup()
									.addPreferredGap(ComponentPlacement.RELATED)
									.addComponent(allItemsButtonAddSupplier)
									.addPreferredGap(ComponentPlacement.RELATED)
									.addComponent(allItemsButtonEditOutsiders)))
							.addGap(91))
						.addComponent(separator, GroupLayout.PREFERRED_SIZE, 205, GroupLayout.PREFERRED_SIZE)
						.addGroup(gl_allItemsInfo.createSequentialGroup()
							.addContainerGap()
							.addComponent(allItemsInfoListOutsidersScrollPane, GroupLayout.PREFERRED_SIZE, 194, GroupLayout.PREFERRED_SIZE)))
					.addContainerGap())
		);
		gl_allItemsInfo.setVerticalGroup(
			gl_allItemsInfo.createParallelGroup(Alignment.TRAILING)
				.addGroup(gl_allItemsInfo.createSequentialGroup()
					.addComponent(separator, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE)
					.addGap(8)
					.addGroup(gl_allItemsInfo.createParallelGroup(Alignment.BASELINE)
						.addComponent(allItemsInfoLabelName, GroupLayout.PREFERRED_SIZE, 19, GroupLayout.PREFERRED_SIZE)
						.addComponent(allItemsInfoValueName))
					.addPreferredGap(ComponentPlacement.RELATED)
					.addGroup(gl_allItemsInfo.createParallelGroup(Alignment.TRAILING)
						.addComponent(allItemsInfoValueType)
						.addComponent(allItemsInfoLabelType))
					.addGap(9)
					.addGroup(gl_allItemsInfo.createParallelGroup(Alignment.BASELINE)
						.addComponent(allItemsInfoLabelPrice, GroupLayout.PREFERRED_SIZE, 17, GroupLayout.PREFERRED_SIZE)
						.addComponent(allItemsInfoValuePrice))
					.addPreferredGap(ComponentPlacement.RELATED)
					.addGroup(gl_allItemsInfo.createParallelGroup(Alignment.BASELINE)
						.addComponent(allItemsInfoLabelStock, GroupLayout.DEFAULT_SIZE, 15, Short.MAX_VALUE)
						.addComponent(allItemsInfoValueStock))
					.addPreferredGap(ComponentPlacement.RELATED)
					.addGroup(gl_allItemsInfo.createParallelGroup(Alignment.BASELINE)
						.addComponent(allItemsInfoLabelDimensions)
						.addComponent(allItemsInfoValueDimensions, GroupLayout.PREFERRED_SIZE, 21, GroupLayout.PREFERRED_SIZE))
					.addPreferredGap(ComponentPlacement.RELATED)
					.addGroup(gl_allItemsInfo.createParallelGroup(Alignment.BASELINE)
						.addComponent(allItemsInfoOutsiders)
						.addComponent(allItemsInfoValueOutsiders))
					.addPreferredGap(ComponentPlacement.UNRELATED)
					.addGroup(gl_allItemsInfo.createParallelGroup(Alignment.BASELINE)
						.addComponent(allItemsButtonAddSupplier, GroupLayout.PREFERRED_SIZE, 20, GroupLayout.PREFERRED_SIZE)
						.addComponent(allItemsButtonEditOutsiders))
					.addGap(3)
					.addComponent(allItemsInfoListOutsidersScrollPane, GroupLayout.PREFERRED_SIZE, 73, GroupLayout.PREFERRED_SIZE))
		);
		allItemsInfo.setLayout(gl_allItemsInfo);
		allItems.setLayout(gl_allItems);

		/******************************************************
		 * 
		 * Item types pane
		 *
		 ******************************************************/

		itemTypes = new ImagePanel(image);

		JPanel itemTypesNew = new JPanel();
		itemTypesNew.setOpaque(false);
		itemTypesNew.setBorder(new TitledBorder(UIManager.getBorder("TitledBorder.border"), "New Item Type", TitledBorder.LEADING, TitledBorder.BELOW_TOP, null, new Color(0, 0, 0)));

		JPanel itemTypesEdit = new JPanel();
		itemTypesEdit.setBorder(new TitledBorder(UIManager.getBorder("TitledBorder.border"), "Edit Item Type", TitledBorder.LEADING, TitledBorder.BELOW_TOP, null, null));
		itemTypesEdit.setOpaque(false);
		GroupLayout gl_itemTypes = new GroupLayout(itemTypes);
		gl_itemTypes.setHorizontalGroup(
				gl_itemTypes.createParallelGroup(Alignment.TRAILING)
				.addGroup(gl_itemTypes.createSequentialGroup()
						.addContainerGap()
						.addComponent(itemTypesNew, GroupLayout.DEFAULT_SIZE, 314, Short.MAX_VALUE)
						.addGap(18)
						.addComponent(itemTypesEdit, GroupLayout.PREFERRED_SIZE, 437, GroupLayout.PREFERRED_SIZE)
						.addContainerGap())
				);
		gl_itemTypes.setVerticalGroup(
				gl_itemTypes.createParallelGroup(Alignment.TRAILING)
				.addGroup(gl_itemTypes.createSequentialGroup()
						.addContainerGap()
						.addGroup(gl_itemTypes.createParallelGroup(Alignment.BASELINE)
								.addComponent(itemTypesEdit, GroupLayout.DEFAULT_SIZE, 259, Short.MAX_VALUE)
								.addComponent(itemTypesNew, GroupLayout.DEFAULT_SIZE, 259, Short.MAX_VALUE))
								.addContainerGap())
				);

		itemTypesEditListTypesModel = new DefaultListModel<String>();
		itemTypesEditListTypes = new JList<String>(itemTypesEditListTypesModel);

		JScrollPane itemTypesEditListScrollPane = new JScrollPane();
		itemTypesEditListScrollPane.setBounds(299, 31, 128, 210);
		itemTypesEditListScrollPane.setOpaque(false);
		itemTypesEditListScrollPane.setBorder(new TitledBorder(UIManager.getBorder("TitledBorder.border"), "Current Item Types", TitledBorder.LEADING, TitledBorder.BELOW_TOP, null, null));
		itemTypesEditListScrollPane.setViewportView(itemTypesEditListTypes);

		itemTypesEditListTypes.setOpaque(false);
		itemTypesEditListTypes.setBorder(null);
		itemTypesEditListTypes.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
		itemTypesEditListTypes.setSelectedIndex(0);
		itemTypesEditListTypes.setVisibleRowCount(4);
		itemTypesEditListTypes.addListSelectionListener(this);

		JLabel itemTypesEditLabelItemTypeName = new JLabel("Item Type Name:");
		itemTypesEditLabelItemTypeName.setBounds(16, 79, 83, 14);

		itemTypesEditTextFieldItemTypeName = new JTextField();
		itemTypesEditTextFieldItemTypeName.setBounds(147, 76, 112, 20);
		itemTypesEditTextFieldItemTypeName.setEnabled(false);

		itemTypesEditButtonItemTypeEdit = new JButton("Edit item type");
		itemTypesEditButtonItemTypeEdit.setBounds(147, 154, 112, 23);
		itemTypesEditButtonItemTypeEdit.setEnabled(false);
		itemTypesEditButtonItemTypeEdit.addActionListener(this);

		itemTypesEditButtonItemTypeEdit.setOpaque(false);

		JLabel itemTypesEditLabelItemTypeMeasurement = new JLabel("Item Type Measurement:");
		itemTypesEditLabelItemTypeMeasurement.setBounds(16, 110, 121, 14);

		itemTypesEditComboBoxMeasurement = new JComboBox<String>();
		itemTypesEditComboBoxMeasurement.setBounds(147, 107, 112, 20);
		itemTypesEditComboBoxMeasurement.setEnabled(false);
		
		JSeparator separator_2 = new JSeparator();
		separator_2.setBounds(6, 20, 424, 11);
		itemTypesEdit.setLayout(null);
		itemTypesEdit.add(itemTypesEditLabelItemTypeName);
		itemTypesEdit.add(itemTypesEditLabelItemTypeMeasurement);
		itemTypesEdit.add(itemTypesEditButtonItemTypeEdit);
		itemTypesEdit.add(itemTypesEditComboBoxMeasurement);
		itemTypesEdit.add(itemTypesEditTextFieldItemTypeName);
		itemTypesEdit.add(itemTypesEditListScrollPane);
		itemTypesEdit.add(separator_2);

		JLabel itemTypesNewLabelItemTypeName = new JLabel("Item Type Name:");
		JLabel itemTypesNewLabelItemTypeMeasurement = new JLabel("Item Type Measurement:");
		JLabel itemTypeMeasurementsEditLabelValue = new JLabel("Measurement Value:");
		itemTypeMeasurementsEditLabelValue.setBounds(16, 89, 98, 14);
		JLabel itemTypeMeasurementsNewLabelValue = new JLabel("Measurement Value:");

		itemTypesNewTextFieldItemTypeName = new JTextField();

		itemTypesNewButtonItemTypeAdd = new JButton("Add item type");
		itemTypesNewButtonItemTypeAdd.setEnabled(false);
		itemTypesNewButtonItemTypeAdd.addActionListener(this);
		itemTypesNewButtonItemTypeAdd.setOpaque(false);

		itemTypesNewComboBoxMeasurement = new JComboBox<String>();
		itemTypesNewComboBoxMeasurement.addActionListener(this);
		
		JSeparator separator_1 = new JSeparator();

		GroupLayout gl_itemTypesNew = new GroupLayout(itemTypesNew);
		gl_itemTypesNew.setHorizontalGroup(
			gl_itemTypesNew.createParallelGroup(Alignment.LEADING)
				.addGroup(gl_itemTypesNew.createSequentialGroup()
					.addContainerGap()
					.addGroup(gl_itemTypesNew.createParallelGroup(Alignment.LEADING)
						.addComponent(itemTypesNewLabelItemTypeName)
						.addComponent(itemTypesNewLabelItemTypeMeasurement))
					.addGap(14)
					.addGroup(gl_itemTypesNew.createParallelGroup(Alignment.TRAILING, false)
						.addComponent(itemTypesNewButtonItemTypeAdd, Alignment.LEADING, GroupLayout.DEFAULT_SIZE, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
						.addComponent(itemTypesNewComboBoxMeasurement, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
						.addComponent(itemTypesNewTextFieldItemTypeName, GroupLayout.DEFAULT_SIZE, 110, Short.MAX_VALUE))
					.addGap(43))
				.addComponent(separator_1, Alignment.TRAILING, GroupLayout.DEFAULT_SIZE, 312, Short.MAX_VALUE)
		);
		gl_itemTypesNew.setVerticalGroup(
			gl_itemTypesNew.createParallelGroup(Alignment.LEADING)
				.addGroup(gl_itemTypesNew.createSequentialGroup()
					.addComponent(separator_1, GroupLayout.PREFERRED_SIZE, 11, GroupLayout.PREFERRED_SIZE)
					.addGap(46)
					.addGroup(gl_itemTypesNew.createParallelGroup(Alignment.BASELINE)
						.addComponent(itemTypesNewLabelItemTypeName)
						.addComponent(itemTypesNewTextFieldItemTypeName, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE))
					.addPreferredGap(ComponentPlacement.UNRELATED)
					.addGroup(gl_itemTypesNew.createParallelGroup(Alignment.BASELINE)
						.addComponent(itemTypesNewLabelItemTypeMeasurement)
						.addComponent(itemTypesNewComboBoxMeasurement, GroupLayout.PREFERRED_SIZE, 22, GroupLayout.PREFERRED_SIZE))
					.addGap(30)
					.addComponent(itemTypesNewButtonItemTypeAdd)
					.addContainerGap(73, Short.MAX_VALUE))
		);
		itemTypesNew.setLayout(gl_itemTypesNew);
		itemTypes.setLayout(gl_itemTypes);

		/******************************************************
		 * 
		 * Item measurements pane
		 *
		 ******************************************************/

		itemTypeMeasurements = new ImagePanel(image);

		JPanel itemTypeMeasurementsNew = new JPanel();
		itemTypeMeasurementsNew.setOpaque(false);
		itemTypeMeasurementsNew.setBorder(new TitledBorder(UIManager.getBorder("TitledBorder.border"), "Item Type Measurements New", TitledBorder.LEADING, TitledBorder.BELOW_TOP, null, null));

		JPanel itemTypeMeasurementsEdit = new JPanel();
		itemTypeMeasurementsEdit.setOpaque(false);
		itemTypeMeasurementsEdit.setBorder(new TitledBorder(UIManager.getBorder("TitledBorder.border"), "Item Type Measurements Edit", TitledBorder.LEADING, TitledBorder.BELOW_TOP, null, null));
		GroupLayout gl_itemTypeMeasurements = new GroupLayout(itemTypeMeasurements);
		gl_itemTypeMeasurements.setHorizontalGroup(
				gl_itemTypeMeasurements.createParallelGroup(Alignment.LEADING)
				.addGroup(gl_itemTypeMeasurements.createSequentialGroup()
						.addContainerGap()
						.addComponent(itemTypeMeasurementsNew, GroupLayout.PREFERRED_SIZE, 314, GroupLayout.PREFERRED_SIZE)
						.addGap(18)
						.addComponent(itemTypeMeasurementsEdit, GroupLayout.DEFAULT_SIZE, 437, Short.MAX_VALUE)
						.addContainerGap())
				);
		gl_itemTypeMeasurements.setVerticalGroup(
				gl_itemTypeMeasurements.createParallelGroup(Alignment.LEADING)
				.addGroup(gl_itemTypeMeasurements.createSequentialGroup()
						.addContainerGap()
						.addGroup(gl_itemTypeMeasurements.createParallelGroup(Alignment.LEADING)
								.addComponent(itemTypeMeasurementsEdit, GroupLayout.DEFAULT_SIZE, 259, Short.MAX_VALUE)
								.addComponent(itemTypeMeasurementsNew, GroupLayout.DEFAULT_SIZE, 259, Short.MAX_VALUE))
								.addContainerGap())
				);

		itemTypeMeasurementsEditTextFieldValue = new JTextField();
		itemTypeMeasurementsEditTextFieldValue.setBounds(132, 86, 119, 20);
		itemTypeMeasurementsEditTextFieldValue.setEnabled(false);

		itemTypesEditListTypeMeasurementsModel = new DefaultListModel<String>();

		itemTypeMeasurementsEditList = new JList<String>(itemTypesEditListTypeMeasurementsModel);
		itemTypeMeasurementsEditList.setOpaque(false);
		itemTypeMeasurementsEditList.setBorder(null);
		itemTypeMeasurementsEditList.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
		itemTypeMeasurementsEditList.setSelectedIndex(0);
		itemTypeMeasurementsEditList.setVisibleRowCount(4);
		itemTypeMeasurementsEditList.addListSelectionListener(this);

		JScrollPane itemTypeMeasurementsEditListScrollPane = new JScrollPane();
		itemTypeMeasurementsEditListScrollPane.setBounds(292, 26, 129, 215);
		itemTypeMeasurementsEditListScrollPane.setOpaque(false);
		itemTypeMeasurementsEditListScrollPane.setBorder(new TitledBorder(UIManager.getBorder("TitledBorder.border"), "Current Measurements", TitledBorder.LEADING, TitledBorder.BELOW_TOP, null, null));
		itemTypeMeasurementsEditListScrollPane.setViewportView(itemTypeMeasurementsEditList);

		itemTypeMeasurementsEditButtonEdit = new JButton("Edit measurement");
		itemTypeMeasurementsEditButtonEdit.setBounds(132, 154, 119, 23);
		itemTypeMeasurementsEditButtonEdit.setEnabled(false);
		itemTypeMeasurementsEditButtonEdit.addActionListener(this);
		itemTypeMeasurementsEdit.setLayout(null);
		itemTypeMeasurementsEdit.add(itemTypeMeasurementsEditLabelValue);
		itemTypeMeasurementsEdit.add(itemTypeMeasurementsEditTextFieldValue);
		itemTypeMeasurementsEdit.add(itemTypeMeasurementsEditButtonEdit);
		itemTypeMeasurementsEdit.add(itemTypeMeasurementsEditListScrollPane);
		
		separator_4 = new JSeparator();
		separator_4.setBounds(9, 21, 420, 8);
		itemTypeMeasurementsEdit.add(separator_4);

		itemTypeMeasurementsNewTextFieldValue = new JTextField();

		itemTypeMeasurementsNewButtonAdd = new JButton("Add measurement");
		itemTypeMeasurementsNewButtonAdd.addActionListener(this);
		
		separator_3 = new JSeparator();

		GroupLayout gl_itemTypeMeasurementsNew = new GroupLayout(itemTypeMeasurementsNew);
		gl_itemTypeMeasurementsNew.setHorizontalGroup(
			gl_itemTypeMeasurementsNew.createParallelGroup(Alignment.LEADING)
				.addGroup(gl_itemTypeMeasurementsNew.createSequentialGroup()
					.addGap(27)
					.addComponent(itemTypeMeasurementsNewLabelValue)
					.addGap(27)
					.addComponent(itemTypeMeasurementsNewTextFieldValue, GroupLayout.PREFERRED_SIZE, 108, GroupLayout.PREFERRED_SIZE)
					.addGap(42))
				.addGroup(gl_itemTypeMeasurementsNew.createSequentialGroup()
					.addGap(87)
					.addComponent(itemTypeMeasurementsNewButtonAdd, GroupLayout.DEFAULT_SIZE, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
					.addGap(96))
				.addComponent(separator_3, Alignment.TRAILING, GroupLayout.DEFAULT_SIZE, 312, Short.MAX_VALUE)
		);
		gl_itemTypeMeasurementsNew.setVerticalGroup(
			gl_itemTypeMeasurementsNew.createParallelGroup(Alignment.LEADING)
				.addGroup(gl_itemTypeMeasurementsNew.createSequentialGroup()
					.addComponent(separator_3, GroupLayout.PREFERRED_SIZE, 13, GroupLayout.PREFERRED_SIZE)
					.addGap(54)
					.addGroup(gl_itemTypeMeasurementsNew.createParallelGroup(Alignment.BASELINE)
						.addComponent(itemTypeMeasurementsNewLabelValue)
						.addComponent(itemTypeMeasurementsNewTextFieldValue, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE))
					.addGap(49)
					.addComponent(itemTypeMeasurementsNewButtonAdd)
					.addContainerGap(77, Short.MAX_VALUE))
		);
		itemTypeMeasurementsNew.setLayout(gl_itemTypeMeasurementsNew);
		itemTypeMeasurements.setLayout(gl_itemTypeMeasurements);

		try
		{
			/*
			 * We need to load:
			 * 
			 * searchItems() - load the items we have
			 * updateItemTypes() - current item types list 
			 * updateItemTypeMeasurements() - current item type measurements list
			 * allOutsidersUpdateTable() - suppliers table on new item tab
			 */

			searchItems();
			updateItemTypes();
			updateItemTypeMeasurements();
			allOutsidersUpdateTable();
		}
		catch (Exception e)
		{
			msgError(allItems, "Could not load properly");
		}
	}

	/**
	 * Our listener for every action which happens.
	 * This is an implemented method which comes from {@link ActionEvent}
	 * 
	 * @param 	e	the event which has triggered the listener
	 * 
	 * @return 	void 
	 */
	@Override
	public void actionPerformed(ActionEvent e)
	{
		if (e.getSource() == allItemsCheckBoxOnlyActiveItems)
		{
			searchItems();
		}
		else if (e.getSource() == allItemsButtonSearchClear)
		{
			allItemsComboBoxSearchType.setSelectedIndex(0);
			allItemsComboBoxSearchTypes.setSelectedIndex(0);
			allItemsTextFieldSearchFor.setText(null);
		}
		else if ((e.getSource() == allItemsComboBoxSearchType) || (e.getSource() == allItemsComboBoxSearchTypes))
		{
			if (startup)
			{
				allItemsTextFieldSearchFor.setText(null);

				searchItems();
			}
		}
		else if (e.getSource() == newItemButtonCreateItem)
		{
			addItem();
		}
		else if (e.getSource() == allItemsButtonEditItem)
		{
			showEditItemDialog();
		}
		else if (e.getSource() == allItemsButtonEditOutsiders)
		{
			showEditItemOutsidersDialog();
		}
		else if (e.getSource() == itemTypesNewButtonItemTypeAdd)
		{
			addItemType();
		}
		else if (e.getSource() == itemTypesEditButtonItemTypeEdit)
		{
			editItemType();
		}
		else if (e.getSource() == itemTypeMeasurementsNewButtonAdd)
		{
			addItemTypeMeasurement();
		}
		else if (e.getSource() == itemTypeMeasurementsEditButtonEdit)
		{
			editItemTypeMeasurement();
		}
		else if (e.getSource() == itemTypesNewComboBoxMeasurement)
		{
			itemTypesNewButtonItemTypeAdd.setEnabled(itemTypesNewComboBoxMeasurement.getSelectedIndex() > 0);
		}
		else if (e.getSource() == allItemsButtonAddStock)
		{
			showAddItemStockDialog();
		}
		else if (e.getSource() == allItemsButtonAddSupplier)
		{
			showAddSupplierDialog();
		}
		else if(e.getSource() == statistics)
			{
				StatisticsUI stats = StatisticsUI.getInstance();
				stats.display();
				frameItemUI.setVisible(false);
			}
		else if (e.getSource() == btnBack)
			{
				
			}
	}

	private void showAddSupplierDialog()
	{
		if (allItemsTable.getSelectedRow() > -1)
		{
			int row = allItemsTable.getSelectedRow();
			int itemID = Integer.valueOf(String.valueOf(allItemsTable.getValueAt(row, 0)));

			try
			{
				ArrayList<Outsider> itemOutsidersOtherList = supplierCtrl.printAllSuppliers(itemID);

				if (itemOutsidersOtherList.size() > 0)
				{
					JPanel panel = new JPanel(new GridLayout(0, 2, 5, 5));

					JComboBox<String> supplierCombobox = new JComboBox<String>();
					JTextField quantityField = new JTextField();

					for (Outsider supplier : itemOutsidersOtherList)
					{
						supplierCombobox.addItem(supplier.getName());
					}

					panel.add(new JLabel("Select a supplier:"));
					panel.add(supplierCombobox);
					panel.add(new JLabel("Quantity:"));
					panel.add(quantityField);

					int option = JOptionPane.showConfirmDialog(null, panel, "Add a supplier", JOptionPane.OK_CANCEL_OPTION);

					if (option == JOptionPane.OK_OPTION)
					{
						if (Number.isNumber(quantityField.getText()))
						{
							Outsider newOutsider = supplierCtrl.searchSupplierByName(supplierCombobox.getSelectedItem().toString());
							int quantity = Integer.valueOf(quantityField.getText());
							int result = itemCtrl.addItemStock(itemID, quantity, newOutsider, false);

							if (result > 0)
							{
								msgSuccess(null, "Successfully added supplier " + newOutsider.getName() + " with " + quantity);
							}
							else
							{
								throw new SQLException();
							}
						}
					}
				}
				else 
				{
					msgError(null, "All the current suppliers are already associated with this item");
				}
			}
			catch (SQLException e)
			{
				msgError(null, "There was an error while adding the supplier");
				e.printStackTrace();
			}
			finally
			{
				searchItems();
				allItemsTable.setRowSelectionInterval(row, row);
				updateItemInfo(itemID);
			}
		}
		else
		{
			msgError(null, "You have not select an item");
		}
	}

	private void showAddItemStockDialog()
	{
		if (allItemsTable.getSelectedRow() > -1)
		{
			int itemID = Integer.valueOf(String.valueOf(allItemsTable.getValueAt(allItemsTable.getSelectedRow(), 0)));
			ArrayList<ItemSupplier> currentSupplierList = new ArrayList<ItemSupplier>();

			try
			{
				currentSupplierList = itemCtrl.getItemSuppliers(itemID, true);
			}
			catch (SQLException e)
			{
				msgError(null, "Could not load suppliers");
			}

			JPanel panel = new JPanel(new GridLayout(0, 2, 5, 5));
			JComboBox<String> supplierComboBox = new JComboBox<String>();
			JTextField quantity = new JTextField();

			updateItemSupplierList(supplierComboBox, currentSupplierList);

			panel.add(new JLabel("Supplier: "));
			panel.add(supplierComboBox);
			panel.add(new JLabel("Quantity: "));
			panel.add(quantity);

			int option = JOptionPane.showConfirmDialog(null, panel, "Add quantity", JOptionPane.OK_OPTION);

			if (option == JOptionPane.YES_OPTION)
			{
				if (Number.isNumber(quantity.getText()))
				{
					try
					{
						int success = itemCtrl.addItemStock(itemID, Integer.valueOf(quantity.getText()), supplierCtrl.searchSupplierByName(supplierComboBox.getSelectedItem().toString()), true);

						if (success < 1)
						{
							throw new SQLException();
						}
					}
					catch(SQLException e)
					{
						msgError(null, "There was an error while adding the quantity");
					}
					finally
					{
						searchItems();
					}
				}
				else 
				{
					msgError(null, "Quantity must be a number");
				}
			}
		}
		else
		{
			msgError(null, "You have not select an item");
		}

	}

	/**
	 * Our list listener. 
	 * This is the implementation of {@link ListSelectionEvent}
	 * 
	 * @param 	e		the event which has triggered the listener
	 * 
	 * @return 	void 
	 */
	@Override
	public void valueChanged(ListSelectionEvent e)
	{
		if (e.getSource() == itemTypesEditListTypes)
		{
			if ((!e.getValueIsAdjusting()) && (itemTypesEditListTypes.getSelectedValue() != null))
			{
				try
				{
					ItemType selectedItemType = itemCtrl.findItemTypeByName(itemTypesEditListTypes.getSelectedValue());

					updateItemTypeMeasurementComboBox(itemTypesEditComboBoxMeasurement, false);

					itemTypesEditTextFieldItemTypeName.setText(selectedItemType.getTypeName());
					itemTypesEditTextFieldItemTypeName.setEnabled(true);

					itemTypesEditComboBoxMeasurement.setSelectedItem(selectedItemType.getTypeMeasurement().getMeasurement());
					itemTypesEditComboBoxMeasurement.setEnabled(true);

					itemTypesEditButtonItemTypeEdit.setEnabled(true);
				}
				catch (SQLException ex)
				{
					msgError(itemTypeMeasurements, "There was an error selecting the item type");
				}        	
			}
		}
		else if (e.getSource() == itemTypeMeasurementsEditList)
		{
			if ((!e.getValueIsAdjusting()) && (itemTypeMeasurementsEditList.getSelectedValue() != null))
			{
				try
				{
					ItemTypeMeasurement selectedItemTypeMeasurement = itemCtrl.findItemTypeMeasurementByName(itemTypeMeasurementsEditList.getSelectedValue());

					itemTypeMeasurementsEditTextFieldValue.setText(selectedItemTypeMeasurement.getMeasurement());
					itemTypeMeasurementsEditTextFieldValue.setEnabled(true);

					itemTypeMeasurementsEditButtonEdit.setEnabled(true);
				}
				catch (SQLException ex)
				{
					msgError(itemTypeMeasurements, "There was an error selecting the measurement type");
				}
			}
		}
		else
		{		
			if (!e.getValueIsAdjusting() && (allItemsTable.getRowCount() > 0) && (allItemsTable.getSelectedRow() >= 0))
			{
				int itemID = Integer.valueOf(String.valueOf(allItemsTable.getValueAt(allItemsTable.getSelectedRow(), 0)));

				updateItemInfo(itemID);
			}
		}
	}

	/** 
	 * Necessary checks when adding a item
	 * 
	 * @return	void
	 */
	private void addItem()
	{
		boolean validInfo = itemCheckValidInfo(newItemTextFields);

		if (validInfo && (newItemOutsiders.size() > 0))
		{
			try
			{
				int success = itemCtrl.createItem(newItemTextFieldName.getText(), Double.valueOf(newItemTextFieldPrice.getText()), Integer.valueOf(newItemTextFieldStock.getText()), newItemTextFieldDimensions.getText(), newItemOutsiders, itemCtrl.findItemTypeByName(newItemComboBoxType.getSelectedItem().toString()));

				if (success > 0)
				{
					msgSuccess(newItem, "Item \"" + newItemTextFieldName.getText() + "\" has been added successfully");

					for(JTextField tf : newItemTextFields)
						tf.setText(null);

					newItemTextFieldDimensions.setText(null);

					newItemOutsiders.clear();

					allOutsidersUpdateTable();
					newItemUpdateSelectedOutsiders();
					searchItems();
				}
				else
				{
					msgError(newItem, "There was an error adding the item.\nThis item name already exists in the system.");					
				}
			}
			catch (Exception ex)
			{
				msgError(newItem, "There was an error adding the item.\nThis item name already exists in the system.");
			}
		}
		else 
		{
			String error = "You cannot proceed due some errors:\n\n";

			if (!validInfo)
				error += " - You haven't filled up every text area or a field exceeds 32 symbols\n";

			if (newItemOutsiders.size() == 0)
				error += " - You haven't selected any suppliers for this item\n";

			msgError(newItem, error);
		}		
	}

	/**
	 * Necessary checks (and dialog opening) when editing an item
	 * 
	 * @return	void
	 */
	private void showEditItemDialog()
	{
		if (allItemsTable.getSelectedRow() > -1) 
		{
			try
			{
				int itemID = Integer.valueOf(String.valueOf(allItemsTable.getValueAt(allItemsTable.getSelectedRow(), 0)));

				Item editItem = itemCtrl.searchItemByID(itemID);

				JPanel panel = new JPanel(new GridLayout(0, 2, 5, 5));

				JTextField editItemTextFieldItemName = new JTextField(editItem.getName());
				JTextField editItemTextFieldItemStock = new JTextField(String.valueOf(editItem.getStock()));
				JTextField editItemTextFieldItemPrice = new JTextField(String.format(Locale.US, "%.2f", editItem.getPrice()));
				JTextField editItemTextFieldItemDimensions = new JTextField(editItem.getDimensions());

				editItemTextFieldItemName.setEditable(false);
				editItemTextFieldItemStock.setEditable(false);

				editItemComboBoxType = new JComboBox<String>();
				updateItemTypeComboBox(editItemComboBoxType, false);
				editItemComboBoxType.setSelectedItem(editItem.getType().getTypeName());			

				panel.add(new JLabel("Item Name:"));
				panel.add(editItemTextFieldItemName);
				panel.add(new JLabel("Item Stock:"));
				panel.add(editItemTextFieldItemStock);
				panel.add(new JLabel("Item Price:"));
				panel.add(editItemTextFieldItemPrice);
				panel.add(new JLabel("Item Dimensions:"));
				panel.add(editItemTextFieldItemDimensions);
				panel.add(new JLabel("Item Type:"));
				panel.add(editItemComboBoxType);

				editItemTextFields = new ArrayList<JTextField>();
				editItemTextFields.add(editItemTextFieldItemName);
				editItemTextFields.add(editItemTextFieldItemStock);
				editItemTextFields.add(editItemTextFieldItemPrice);

				int option = JOptionPane.showConfirmDialog(allItems, panel, "Edit Item", JOptionPane.OK_CANCEL_OPTION);

				if (option == JOptionPane.YES_OPTION)
				{
					boolean validInfo = itemCheckValidInfo(editItemTextFields);

					String stock = editItemTextFieldItemStock.getText();
					String price = editItemTextFieldItemPrice.getText();

					if (validInfo && Number.isNumber(stock) && Number.isDouble(price))
					{
						int success = itemCtrl.updateItem(itemID, editItemTextFieldItemName.getText(), Double.valueOf(price), Integer.valueOf(stock), editItemTextFieldItemDimensions.getText(), itemCtrl.findItemTypeByName(editItemComboBoxType.getSelectedItem().toString()));

						if (success > 0)
						{
							msgSuccess(newItem, "Item #" + itemID + " has been edited successfully");

							searchItems();
						}
						else 
						{
							msgError(newItem, "There was an error editing the item");
						}
					}
					else 
					{
						String error = "You cannot proceed due some errors:\n\n";

						if (!validInfo)
							error += " - You haven't filled up every text area\n";

						if (!Number.isNumber(stock))
							error += " - Stock is not a valid number\n";

						if (!Number.isDouble(price))
							error += " - Price is not a valid number\n";

						msgError(newItem, error);
					}
				}
			}
			catch (SQLException ex)
			{
				msgError(allItems, "There was a problem loading the item");
			}
		}
		else 
		{
			msgError(allItems, "You have not selected a item");
		}
	}

	/** 
	 * Necessary checks (and dialog opening) to update item's suppliers.
	 * 
	 * @return	void
	 */
	private void showEditItemOutsidersDialog()
	{
		if (allItemsTable.getSelectedRow() > -1) 
		{
			int row = allItemsTable.getSelectedRow();
			int itemID = Integer.valueOf(String.valueOf(allItemsTable.getValueAt(row, 0)));

			try
			{
				String[] tableColumns = { "#", "Supplier", "", "Quantity", "Active" };
				double[] tableWidth = { 0.3, 2, 0.3, 1, 1 };

				JPanel panel = new JPanel(new GridLayout(0, 1, 5, 5));

				itemEditOutsidersList = itemCtrl.getItemSuppliers(itemID, false);

				DefaultTableModel allItemsEditItemOutsidersTableModel = new DefaultTableModel(null, tableColumns);

				allItemsEditItemOutsidersTable = new JTable(allItemsEditItemOutsidersTableModel)
				{
					private static final long serialVersionUID = 1L;

					public boolean isCellEditable(int rowIndex, int colIndex) 
					{
						return false;
					}

					public Class<?> getColumnClass(int column)   
					{   
						return getValueAt(0, column).getClass();   
					}
				};
				allItemsEditItemOutsidersTable.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);

				allItemsEditItemOutsidersTable.addMouseListener(
						new MouseAdapter() 
						{
							public void mouseClicked(MouseEvent e) 
							{
								int itemID = Integer.valueOf(String.valueOf(allItemsTable.getValueAt(allItemsTable.getSelectedRow(), 0)));
								int supplierID = Integer.valueOf(String.valueOf(allItemsEditItemOutsidersTable.getValueAt(allItemsEditItemOutsidersTable.getSelectedRow(), 0)));
								int result = 0;

								String active = String.valueOf(allItemsEditItemOutsidersTable.getValueAt(allItemsEditItemOutsidersTable.getSelectedRow(), 4));

								try
								{
									result = itemCtrl.updateItemSupplierStatus(itemID, supplierID);
								}
								catch (SQLException ex)
								{
									msgError(null, "Could not update supplier status");
								}

								if (result > 0)
								{	
									allItemsEditItemOutsidersTable.setValueAt(new ImageIcon("img/tick_" + (active.contains("yes") ? "no" : "yes") + ".png"), allItemsEditItemOutsidersTable.getSelectedRow(), 4);
								}
								else
								{
									msgError(null, "There was an error while changing status");
								}
							}
						});

				tableDimension = allItemsEditItemOutsidersTable.getPreferredSize(); 

				columnWidth = tableDimension.width / tableColumns.length; 

				for (int i = 0; i < tableColumns.length; i++)
					allItemsEditItemOutsidersTable.getColumnModel().getColumn(i).setPreferredWidth((int) (columnWidth*tableWidth[i])); 

				JScrollPane allItemsEditItemOutsidersTableScrollPane = new JScrollPane();
				allItemsEditItemOutsidersTable.setPreferredScrollableViewportSize(new Dimension(300, 160));
				allItemsEditItemOutsidersTableScrollPane.setViewportView(allItemsEditItemOutsidersTable);

				for(ItemSupplier supplier : itemEditOutsidersList)
				{
					allItemsEditItemOutsidersTableModel.addRow(
							new Object[]
									{
									supplier.getOutsider().getOutsiderID(),
									supplier.getOutsider().getName(),
									new ImageIcon("img/flags/" + supplier.getOutsider().getCity().getCountry().getTld() + ".png"),
									supplier.getQuantity(),
									new ImageIcon("img/tick_" + (supplier.isActive() ? "yes" : "no") + ".png")
									});

				}

				panel.add(allItemsEditItemOutsidersTableScrollPane);

				JOptionPane.showMessageDialog(allItems, panel, "Edit supplier status", JOptionPane.INFORMATION_MESSAGE);
			}
			catch (SQLException e)
			{
				msgError(allItems, "Could not load item info");
			}
			finally
			{
				searchItems();
				allItemsTable.setRowSelectionInterval(row, row);
				updateItemInfo(itemID);
			}
		}
		else 
		{
			msgError(allItems, "You have not selected an item");
		}
	}

	/** 
	 * Necessary checks when adding an item type.
	 * 
	 * @return	void
	 */
	private void addItemType()
	{
		if ((itemTypesNewTextFieldItemTypeName.getText().trim().length() > 0) && (itemTypesNewTextFieldItemTypeName.getText().length() <= 100)) 
		{
			try
			{
				int success = itemCtrl.createItemType(itemCtrl.findItemTypeMeasurementByName(itemTypesNewComboBoxMeasurement.getSelectedItem().toString()), itemTypesNewTextFieldItemTypeName.getText());

				if (success > 0)
				{
					updateItemTypes();

					msgSuccess(itemTypes, "Item Type \"" + itemTypesNewTextFieldItemTypeName.getText() + "\" was added successfully");

					itemTypesNewTextFieldItemTypeName.setText(null);
					itemTypesNewComboBoxMeasurement.setSelectedIndex(0);
				}
				else 
				{
					msgError(itemTypes, "There is already item type with the same name");					
				}
			}
			catch (SQLException e)
			{
				msgError(itemTypes, "There was a problem while adding the item type");
			}
		}
		else 
		{
			msgError(itemTypes, "You have not written an item type name or it is over 100 symbols");
		}
	}

	/** 
	 * Necessary checks when editing an item type.
	 * 
	 * @return	void
	 */
	private void editItemType()
	{
		if (!itemTypesEditListTypes.isSelectionEmpty())
		{
			if ((itemTypesEditTextFieldItemTypeName.getText().trim().length() > 0) && (itemTypesEditTextFieldItemTypeName.getText().length() <= 100))
			{
				try
				{
					ItemType selectedItemType = itemCtrl.findItemTypeByName(itemTypesEditListTypes.getSelectedValue());

					int success = itemCtrl.updateItemType(selectedItemType.getTypeID(), itemCtrl.findItemTypeMeasurementByName(itemTypesEditComboBoxMeasurement.getSelectedItem().toString()), itemTypesEditTextFieldItemTypeName.getText());

					if (success > 0)
					{
						msgSuccess(itemTypes, "Item type \"" + selectedItemType.getTypeName() + "\" is successfully edited and is now known as \"" + itemTypesEditTextFieldItemTypeName.getText() + "\"");

						updateItemTypes();

						itemTypesEditTextFieldItemTypeName.setText(null);
						itemTypesEditTextFieldItemTypeName.setEnabled(false);

						itemTypesEditComboBoxMeasurement.setSelectedIndex(0);
						itemTypesEditComboBoxMeasurement.setEnabled(false);

						itemTypesEditButtonItemTypeEdit.setEnabled(false);						
					}
					else 
					{
						msgError(itemTypes, "There is already item type with the same name");					
					}
				}
				catch (SQLException e)
				{
					msgError(itemTypes, "There was a problem while adding the item type");
				}
			}
			else 
			{
				msgError(itemTypes, "You have not written an item type name or it is over 100 symbols");
			}
		}
		else 
		{
			msgError(itemTypes, "You have not selected an item type");			
		}
	}

	/** 
	 * Necessary checks when adding an item type measurement.
	 * 
	 * @return	void
	 */
	private void addItemTypeMeasurement()
	{
		if ((itemTypeMeasurementsNewTextFieldValue.getText().trim().length() > 0) && (itemTypeMeasurementsNewTextFieldValue.getText().length() <= 100)) 
		{
			try
			{
				int success = itemCtrl.createItemTypeMeasurement(itemTypeMeasurementsNewTextFieldValue.getText());

				if (success > 0)
				{
					updateItemTypeMeasurements();
					msgSuccess(itemTypes, "Item type measurement \"" + itemTypeMeasurementsNewTextFieldValue.getText() + "\" was added successfully");

					itemTypeMeasurementsNewTextFieldValue.setText(null);
				}
				else 
				{
					msgError(itemTypes, "There is already the same item type measurement");					
				}
			}
			catch (SQLException e)
			{
				msgError(itemTypes, "There was a problem while adding the item type measurement");
			}
		}
		else 
		{
			msgError(itemTypes, "You have not written an item type name or it is over 100 symbols");
		}
	}

	/** 
	 * Necessary checks when editing an item type measurement.
	 * 
	 * @return	void
	 */
	private void editItemTypeMeasurement()
	{
		if (!itemTypeMeasurementsEditList.isSelectionEmpty())
		{
			if ((itemTypeMeasurementsEditTextFieldValue.getText().trim().length() > 0) && (itemTypeMeasurementsEditTextFieldValue.getText().length() <= 100))
			{
				try
				{
					ItemTypeMeasurement selectedItemTypeMeasurement = itemCtrl.findItemTypeMeasurementByName(itemTypeMeasurementsEditList.getSelectedValue());

					int success = itemCtrl.updateItemTypeMeasurement(selectedItemTypeMeasurement.getID(), itemTypeMeasurementsEditTextFieldValue.getText());

					if (success > 0)
					{
						msgSuccess(itemTypes, "Item type measurement \"" + selectedItemTypeMeasurement.getMeasurement() + "\" is successfully edited and is now known as \"" + itemTypeMeasurementsEditTextFieldValue.getText() + "\"");

						updateItemTypeMeasurements();

						itemTypeMeasurementsEditTextFieldValue.setText(null);
						itemTypeMeasurementsEditTextFieldValue.setEnabled(false);

						itemTypeMeasurementsEditButtonEdit.setEnabled(false);
					}
					else
					{
						msgError(itemTypes, "There is already the same item type measurement");
					}
				}
				catch (SQLException e)
				{
					msgError(itemTypes, "There was a problem while updating the item type measurement");
				}
			}
			else 
			{
				msgError(itemTypes, "You have not written an item type name or it is over 100 symbols");
			}
		}
		else 
		{
			msgError(itemTypes, "You have not selected an item type measure");			
		}
	}

	/** 
	 * Remove a supplier from our temporary list.
	 * 
	 * @param 	list			The list with suppliers we're going to search through
	 * @param	supplierID		he desired supplier ID we want to remove.
	 * 
	 * @return	void
	 */
	private void itemOutsidersRemoveFromList(ArrayList<ItemSupplier> list, int supplierID)
	{	
		Iterator<ItemSupplier> it = list.iterator();

		boolean found = false;

		while (it.hasNext() && !found)
		{
			if(it.next().getOutsider().getOutsiderID() == supplierID)
			{
				it.remove();
				found = true;
			}
		}

	}

	/** 
	 * Adding suppliers to the table.
	 * 
	 * @return	void
	 */
	private void newItemUpdateSelectedOutsiders()
	{
		tableClearList(newItemTableSelected);

		int itemStock = 0;

		for(ItemSupplier it : newItemOutsiders)
		{
			tableOutsidersAddQuantity(newItemModelSelected, it.getOutsider(), it.getQuantity());
			itemStock += it.getQuantity();
		}

		newItemTextFieldStock.setText(String.valueOf(itemStock));
	}

	/** 
	 * Adding a supplier object as a row to any {@link DefaultTableModel}
	 * 
	 * @param	model		the table model where we are going to add the row
	 * @param	supplier	the supplier object we are going to add 
	 * 
	 * @return	void
	 */
	private void tableOutsidersAdd(DefaultTableModel model, Outsider supplier)
	{
		model.addRow(
				new Object[] 
						{
						supplier.getOutsiderID(),
						supplier.getName(),
						new ImageIcon("img/flags/" + supplier.getCity().getCountry().getTld() + ".png")
						}
				);
	}

	/** 
	 * Adding a supplier object as a row to any {@link DefaultTableModel}
	 * 
	 * @param	model		the table model where we are going to add the row
	 * @param	supplier	the supplier object we are going to add 
	 * 
	 * @return	void
	 */
	private void tableOutsidersAddQuantity(DefaultTableModel model, Outsider supplier, int quantity)
	{
		model.addRow(
				new Object[] 
						{
						supplier.getOutsiderID(),
						supplier.getName(),
						new ImageIcon("img/flags/" + supplier.getCity().getCountry().getTld() + ".png"),
						quantity
						}
				);
	}

	/** 
	 * Updating the Item Info box when selecting an item on the main item table
	 * 
	 * @param	itemID		the selected item's ID
	 * 
	 * @return	void
	 */
	private void updateItemInfo(int itemID)
	{		
		try
		{
			Item itemInfo = itemCtrl.searchItemByID(itemID);
			ArrayList<ItemSupplier> itemSupplierList = itemCtrl.getItemSuppliers(itemID, false);
			supplierFlagList = new ArrayList<String>();

			allItemsInfoValueName.setText(itemInfo.getName());
			allItemsInfoValuePrice.setText(String.valueOf(itemInfo.getPrice()));
			allItemsInfoValueStock.setText(String.valueOf(itemInfo.getStock()) + " " + itemInfo.getType().getTypeMeasurement().getMeasurement());
			allItemsInfoValueDimensions.setText(itemInfo.getDimensions().length() > 0 ? itemInfo.getDimensions() : "n/a");
			allItemsInfoValueOutsiders.setText(String.valueOf(itemSupplierList.size()));
			allItemsInfoValueType.setText(itemInfo.getType().getTypeName());

			allItemsButtonEditOutsiders.setEnabled(true);
			allItemsButtonAddSupplier.setEnabled(true);
			allItemsInfoListOutsidersModel.removeAllElements();

			for(ItemSupplier itemSuppliers : itemSupplierList)
			{
				String itemSupplier = (itemSuppliers.isActive() ? "<html><b>" : "") + itemSuppliers.getOutsider().getName() + (itemSuppliers.isActive() ? "</b></html>" : "");

				supplierFlagList.add(itemSuppliers.getOutsider().getCity().getCountry().getTld());
				allItemsInfoListOutsidersModel.addElement(itemSupplier);
			}			
		}
		catch (SQLException e)
		{
			msgError(null, "Could not load item info");
		}
	}

	/** 
	 * Updating a combo box which should have item type values
	 * 
	 * @param 	comboBox		which combo box to update
	 * 
	 * @return	void
	 */
	private void updateItemSupplierList(JComboBox<String> comboBox, ArrayList<ItemSupplier> currentSupplierList)
	{
		comboBox.removeAllItems();

		try
		{
			for(ItemSupplier supplier : currentSupplierList)
				comboBox.addItem(supplier.getOutsider().getName());
		}
		catch(Exception e)
		{
			msgError(newItem, "Could not load suppliers");
		}
	}

	/** 
	 * Updating everything which is connected with ItemTypes (combo boxes, lists)
	 * 
	 * @return	void
	 */
	private void updateItemTypes()
	{
		try
		{
			itemTypeList = itemCtrl.printAllItemTypes();

			updateItemTypeComboBox(allItemsComboBoxSearchTypes, true);
			updateItemTypeComboBox(newItemComboBoxType, false);
			updateItemTypeList();
		}
		catch(Exception e)
		{
			msgError(newItem, "Could not load item types");
		}
	}

	/** 
	 * Updating the item type list.
	 * 
	 * @return	void
	 */	
	private void updateItemTypeList()
	{
		itemTypesEditListTypesModel.removeAllElements();

		for (ItemType itemtype : itemTypeList)
		{
			itemTypesEditListTypesModel.addElement(itemtype.getTypeName());	
		}		
	}

	/** 
	 * Updating a combo box which should have item type values
	 * 
	 * @param 	comboBox		which combo box to update
	 * @param	emptyField		if true adds an empty/fake "All types" on the top
	 * 
	 * @return	void
	 */
	private void updateItemTypeComboBox(JComboBox<String> comboBox, boolean emptyField)
	{
		comboBox.removeAllItems();

		if (emptyField)
			comboBox.addItem("All types");

		try
		{
			for(ItemType item : itemTypeList)
				comboBox.addItem(item.getTypeName());
		}
		catch(Exception e)
		{
			msgError(newItem, "Could not load item types");
		}
	}

	/** 
	 * Updates everything which is connected to item type measurements (combo box, list)
	 * 
	 * @return	void
	 */
	private void updateItemTypeMeasurements()
	{
		try
		{
			itemTypeMeasurementList = itemCtrl.printAllItemTypeMeasurement();

			updateItemTypeMeasurementComboBox(itemTypesNewComboBoxMeasurement, true);
			updateItemTypeMeasurementList();
		}
		catch(Exception e)
		{
			msgError(newItem, "Could not load item type measurements");
		}
	}

	/** 
	 * Updates item type measurement's list
	 * 
	 * @return		void
	 */
	private void updateItemTypeMeasurementList()
	{
		itemTypesEditListTypeMeasurementsModel.removeAllElements();

		for (ItemTypeMeasurement measure : itemTypeMeasurementList)
		{
			itemTypesEditListTypeMeasurementsModel.addElement(measure.getMeasurement());
		}
	}

	/** 
	 * Updating a combo box which should have item type measurements values
	 * 
	 * @param 	comboBox	which combo box to update
	 * @param	notEmpty	if true adds an empty/fake "All types" on the top
	 * 
	 * @return	void
	 */
	private void updateItemTypeMeasurementComboBox(JComboBox<String> comboBox, boolean notEmpty)
	{
		comboBox.removeAllItems();

		if (notEmpty)
			comboBox.addItem(null);

		try
		{
			for(ItemTypeMeasurement measurement : itemTypeMeasurementList)
				comboBox.addItem(measurement.getMeasurement());
		}
		catch(Exception e)
		{
			msgError(newItem, "Could not load item type measurements");
		}
	}

	/**
	 * Updating the all item type table
	 *
	 * @param  	itemList 	the array list which is put in the table
	 * 
	 * @return	void
	 */
	private void allItemsUpdateTable(LinkedList<Item> itemList)
	{
		if (itemList.size() > 0)
		{
			tableClearList(allItemsTable);

			for(Item item : itemList)
			{
				allItemsTableModel.addRow(
						new Object[]
								{
								item.getItemID(), 
								item.getName(),
								item.getStock(),
								item.getType().getTypeMeasurement().getMeasurement(),
								item.getPrice(),
								item.getType().getTypeName(),
								item.getDimensions()
								} 
						);
			}
		}
	}

	/** 
	 * Updates the supplier table
	 * 
	 * @return	void
	 */
	private void allOutsidersUpdateTable()
	{
		try
		{
			supplierList = supplierCtrl.printAllSuppliers(0);

			if (supplierList.size() > 0)
			{
				tableClearList(newItemTableAll);

				for(Outsider supplier : supplierList)
				{
					tableOutsidersAdd(newItemModelAll, supplier);
				}
			}
		}
		catch (SQLException e)
		{
			msgError(null, "Could not update supliers table");
		}
	}


	/**
	 * Returns if the two ArrayLists which are given are not empty
	 *
	 * @param  	textFields 		an array list with all the text fields which need to be checked
	 * 
	 * @return	boolean			true, if they are not empty
	 */
	private boolean itemCheckValidInfo(ArrayList<JTextField> textFields)
	{
		for(JTextField tf : textFields)
		{
			if ((tf.getText().trim().length() == 0) || (tf.getText().trim().length() > 32))
				return false;
		}

		return true;
	}

	/**
	 * Removing all rows from the any table
	 *
	 * @return	void
	 */
	private void tableClearList(JTable table)
	{
		DefaultTableModel dm = (DefaultTableModel) table.getModel();

		while(dm.getRowCount() > 0)
			dm.removeRow(0);
	}

	/**
	 * Searching items based on the selected drop down criteria 
	 * and input text field
	 * 
	 * @return	void
	 */
	private void searchItems()
	{
		LinkedList<Item> itemList = new LinkedList<Item>();

		allItemsInfoValueName.setText("n/a");
		allItemsInfoValuePrice.setText("0");
		allItemsInfoValueStock.setText("0");
		allItemsInfoValueDimensions.setText(null);
		allItemsInfoValueOutsiders.setText("0");
		allItemsInfoValueType.setText("n/a");
		allItemsInfoListOutsidersModel.removeAllElements();
		allItemsButtonEditOutsiders.setEnabled(false);
		allItemsButtonAddSupplier.setEnabled(false);

		boolean active = allItemsCheckBoxOnlyActiveItems.isSelected();

		String clause = allItemsComboBoxSearchType.getSelectedItem().toString().toLowerCase();
		String search = allItemsTextFieldSearchFor.getText();
		String type = allItemsComboBoxSearchTypes.getSelectedIndex() > 0 ? allItemsComboBoxSearchTypes.getSelectedItem().toString() : "";

		try
		{
			switch (clause)
			{
				case "everything": 	itemList = itemCtrl.searchItemEverything(active, type, search); break;
				case "name":		itemList = itemCtrl.searchItemName(active, type, search); break;
				case "supplier":	itemList = itemCtrl.searchItemSupplier(active, type, search); break;
				case "city":		itemList = itemCtrl.searchItemCity(active, type, search); break;
				case "country":		itemList = itemCtrl.searchItemCountry(active, type, search); break;
			}

			if (itemList.size() > 0)
				allItemsUpdateTable(itemList);
			else
				tableClearList(allItemsTable);
		}
		catch (Exception e)
		{
			msgError(allItems, "Could not load items");
		}

		if (!startup)
			startup = true;
	}

	/**
	 * Shows an error message pop-up
	 * 
	 * @param	panel 		on which panel should it show the message
	 * @param	error		the error which is printed on the pop-up window
	 * 
	 * @return	void
	 */
	private void msgError(JPanel panel, String error)
	{
		JOptionPane.showConfirmDialog(panel, error, "Error", JOptionPane.PLAIN_MESSAGE, JOptionPane.ERROR_MESSAGE);
	}

	/**
	 * Shows a success message pop-up
	 * 
	 * @param	panel 		on which panel should it show the message
	 * @param	success		the success message which is printed on the pop-up window
	 * 
	 * @return	void
	 */
	private void msgSuccess(JPanel panel, String success)
	{
		JOptionPane.showMessageDialog(panel, success, "Success", 1);
	}

	public static ItemUI getInstance()
	{
		if(instance == null)
			instance = new ItemUI();

		return instance;			
	}

	public static void main(String[] args)
	{
		try 
		{
			UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName()); 

			ItemUI itemMenu = new ItemUI();
			itemMenu.display();
		}
		catch(Exception e)
		{
			JOptionPane.showMessageDialog(null, "Item Menu could not load");
		}
	}
}